<template>
  <el-card shadow="hover" class="hmi-batch-delete-table">
    <!-- 工具栏 -->
    <HmiTableToolbar
      v-if="showToolbar"
      :loading="loading"
      :show-refresh="true"
      :show-export="true"
      @refresh="handleRefresh"
      @export="handleExport"
    >
      <template #right-extra>
        <el-button v-if="config.features.isAdd" type="success" :icon="Plus" @click="handleAdd">
          新增
        </el-button>
        <el-button
          v-if="config.features.isBatchReset"
          :disabled="selectedIds.length === 0"
          type="primary"
          :icon="RefreshRight"
          @click="handleBatchReset"
        >
          批量重置
        </el-button>
        <el-button
          v-if="config.features.isBatchDelete"
          type="danger"
          :disabled="selectedIds.length === 0"
          :icon="Delete"
          @click="handleBatchDelete"
        >
          批量删除
        </el-button>
        <el-button
          v-if="config.features.isBatchTrans"
          type="primary"
          :disabled="selectedIds.length === 0"
          :icon="Promotion"
          @click="handleBatchTrans"
        >
          批量传动
        </el-button>
        <el-button
          v-if="config.features.isBatchPoint"
          type="primary"
          :disabled="selectedIds.length === 0"
          :icon="Pointer"
          @click="handleBatchPoint"
        >
          <!-- <el-icon><Pointer /></el-icon> -->
          批量对点
        </el-button>
        <el-button
          v-if="config.features.isBatchPoint"
          type="primary"
          :icon="Promotion"
          :disabled="isAutoPointingLoading"
          @click="handleAutoPoint"
        >
          {{ isAutoPointing ? "取消自动对点" : "自动对点" }}
        </el-button>
      </template>
    </HmiTableToolbar>

    <!-- 自动对点进度条 -->
    <div v-if="isAutoPointing" class="auto-point-progress">
      <el-progress :percentage="autoPointProgress" :status="autoPointStatus" :stroke-width="10" text-inside />
      <div class="progress-info">正在对点: {{ autoPointCurrentIndex }} / {{ autoPointTotalCount }}</div>
    </div>

    <!-- 表格 -->
    <el-table
      ref="tableRef"
      v-loading="loading"
      :data="tableData"
      :highlight-current-row="highlightCurrentRow"
      border
      class="hmi-batch-delete-table__content"
      @selection-change="handleSelectionChange"
      @row-click="handleRowClick"
    >
      <!-- 选择列 -->
      <el-table-column type="selection" width="55" align="center" />

      <!-- 数据列 -->
      <el-table-column
        v-for="(column, index) in config.columns"
        :key="index"
        :label="column.label"
        :width="column.width"
        :min-width="column.minWidth || 120"
        :align="column.align || 'left'"
      >
        <template #default="{ row }">
          <!-- <span>{{ formatCellValue(row, column) }}</span> -->
          <el-switch
            v-if="isBooleanColumn(row, column)"
            :model-value="Boolean(row[column.key])"
            :disabled="true"
            size="small"
            class="readonly-switch"
          />
          <span v-else>
            {{ formatCellValue(row, column) }}
          </span>
        </template>
      </el-table-column>

      <!-- 操作列 -->
      <el-table-column v-if="showActions" fixed="right" label="操作" :width="getActionsWidth()">
        <template #default="{ row }">
          <el-button
            v-if="config.features.isDownload"
            type="primary"
            size="small"
            link
            :icon="Download"
            @click="handleDownload(row)"
          >
            下载
          </el-button>
          <el-button
            v-if="config.features.isReset"
            type="primary"
            size="small"
            link
            :icon="RefreshRight"
            @click="handleReset(row)"
          >
            重置
          </el-button>
          <el-button
            v-if="config.features.isDelete"
            type="danger"
            size="small"
            link
            :icon="Delete"
            @click="handleDelete(row)"
          >
            删除
          </el-button>
          <el-button
            v-if="config.features.isTrans"
            type="primary"
            size="small"
            link
            :icon="Promotion"
            @click="handleTrans(row)"
          >
            传动
          </el-button>
          <el-button
            v-if="config.features.isPoint"
            type="primary"
            size="small"
            link
            :icon="Pointer"
            @click="handlePoint(row)"
          >
            对点
          </el-button>
        </template>
      </el-table-column>
    </el-table>

    <!-- 分页 -->
    <OffsetPagination
      v-if="total > 0"
      v-model:offset="pagination.offset"
      v-model:limit="pagination.limit"
      :total="total"
      :page-sizes="[10, 20, 50, 100]"
      :layout="paginationLayout"
      class="hmi-batch-delete-table__pagination"
      @pagination="onPagination"
    />
  </el-card>
</template>

<script setup lang="ts">
import { Pointer, Plus, Delete, Promotion, Download, RefreshRight } from "@element-plus/icons-vue";
import { useHmiBatchDeleteData, useHmiBatchDeleteOperations } from "@/composables";
import { useTableExport } from "@/composables/useTableExport";
import { isBooleanColumn, createCellFormatter } from "@/utils/hmi-data-table";
import type { HmiBatchDeleteConfig, HmiBatchDeleteRow } from "./types";
import { OperationType } from "./types";

interface Props {
  config: HmiBatchDeleteConfig;
  showToolbar?: boolean;
  showActions?: boolean;
  highlightCurrentRow?: boolean;
}

interface Emits {
  (e: "data-loaded", data: HmiBatchDeleteRow[]): void;
  (e: "selection-change", selection: HmiBatchDeleteRow[]): void;
  (e: "row-click", row: HmiBatchDeleteRow): void;
  (e: "operation-success", type: string, data: any): void;
  (e: "error", error: Error): void;
}

const props = withDefaults(defineProps<Props>(), {
  showToolbar: true,
  showActions: true,
  highlightCurrentRow: true,
});

const emit = defineEmits<Emits>();

// 使用数据管理 composable
const {
  tableData,
  total,
  selectedRows,
  selectedIds,
  pagination,
  loading,
  hasData,
  currentPage,
  fetchData,
  refreshData,
  handleSelectionChange: handleDataSelectionChange,
  handlePageSizeChange: handleDataPageSizeChange,
  handleCurrentPageChange: handleDataCurrentPageChange,
  handlePaginationChange,
} = useHmiBatchDeleteData(props.config);

// 使用操作 composable
const {
  batchDelete,
  batchReset,
  batchTrans,
  batchPoint,
  autoPoint,
  deleteRow,
  resetRow,
  transRow,
  downloadData,
} = useHmiBatchDeleteOperations(props.config);

// 自动对点相关状态
const isAutoPointing = ref(false);
const isAutoPointingLoading = ref(false);
const autoPointProgress = ref(0);
const autoPointCurrentIndex = ref(0);
const autoPointTotalCount = ref(0);
const autoPointStatus = ref<"success" | "exception" | "">("");
const autoPointAbortController = ref<AbortController | null>(null);

// 使用导出 composable
const { exportToExcel, generateExportColumns } = useTableExport();

// 统一的单元格格式化
// 参数化 valueKey/enumKey，默认回退到 Value/Enum
const valueKey = (props.config as any)?.valueKey ?? "Value";
const enumKey = (props.config as any)?.enumKey ?? "Enum";
const formatCellValue = createCellFormatter({ valueKey, enumKey });

// 计算属性
const paginationLayout = computed(() => {
  return props.config.pagination?.showSizeChanger
    ? "total, sizes, prev, pager, next, jumper"
    : "total, prev, pager, next, jumper";
});

// 获取操作列宽度
function getActionsWidth(): number {
  let width = 0;
  const features = props.config.features;

  if (features.isDownload) width += 80;
  if (features.isReset) width += 80;
  if (features.isDelete) width += 80;
  if (features.isTrans) width += 80;

  return Math.max(width, 120);
}

// 事件处理
function handleSelectionChange(selection: HmiBatchDeleteRow[]) {
  handleDataSelectionChange(selection);
  emit("selection-change", selection);
}

function handleRowClick(row: HmiBatchDeleteRow) {
  emit("row-click", row);
}

function handlePageSizeChange(pageSize: number) {
  handleDataPageSizeChange(pageSize).then(() => {
    emit("data-loaded", tableData.value);
  });
}

function handleCurrentPageChange(page: number) {
  handleDataCurrentPageChange(page).then(() => {
    emit("data-loaded", tableData.value);
  });
}

async function onPagination() {
  await handlePaginationChange();
  emit("data-loaded", tableData.value);
}

// 操作确认
async function confirmOperation(
  type: OperationType,
  message: string,
  operation: () => Promise<any>
) {
  try {
    await ElMessageBox.confirm(message, "确认操作", {
      confirmButtonText: "确定",
      cancelButtonText: "取消",
      type: "warning",
    });

    const result = await operation();
    if (result.status === "Success" || result.status === "success") {
      ElMessage.success("操作成功");
      emit("operation-success", type, result);
      await refreshData();
      emit("data-loaded", tableData.value);
    }
  } catch (error) {
    if (error !== "cancel") {
      const errorInstance = error instanceof Error ? error : new Error(String(error));
      ElMessage.error(`操作失败: ${errorInstance.message}`);
      emit("error", errorInstance);
    }
  }
}

// 工具栏操作
function handleAdd() {
  ElMessage.info("新增功能开发中");
}

function handleBatchReset() {
  confirmOperation(
    OperationType.BATCH_RESET,
    `确认重置已选中的 ${selectedIds.value.length} 条数据？`,
    () => batchReset(selectedIds.value)
  );
}

function handleBatchDelete() {
  confirmOperation(
    OperationType.BATCH_DELETE,
    `确认删除已选中的 ${selectedIds.value.length} 条数据？`,
    () => batchDelete(selectedIds.value)
  );
}

function handleBatchTrans() {
  confirmOperation(
    OperationType.BATCH_TRANS,
    `确认传动已选中的 ${selectedRows.value.length} 条数据？`,
    () => batchTrans(selectedRows.value)
  );
}

async function handleBatchPoint() {
  if (!selectedRows.value.length) {
    ElMessage.warning("请选择要对点的数据");
    return;
  }

  try {
    await ElMessageBox.confirm(
      `确定要对选中的 ${selectedRows.value.length} 条数据进行批量对点吗？`,
      "批量对点确认",
      {
        confirmButtonText: "确定",
        cancelButtonText: "取消",
        type: "warning",
      }
    );

    // 设置批量对点状态
    isAutoPointing.value = true;
    isAutoPointingLoading.value = true;
    autoPointStatus.value = "";
    autoPointProgress.value = 0;
    autoPointCurrentIndex.value = 0;
    autoPointTotalCount.value = selectedRows.value.length;

    // 创建 AbortController 用于取消操作
    autoPointAbortController.value = new AbortController();
    isAutoPointingLoading.value = false;

    let successCount = 0;
    let failCount = 0;

    // 逐条对点
    for (let i = 0; i < selectedRows.value.length; i++) {
      if (!autoPointAbortController.value || autoPointAbortController.value.signal.aborted) {
        ElMessage.info("已取消批量对点");
        break;
      }

      const row = selectedRows.value[i];
      try {
        await batchPoint([row]);
        successCount++;
      } catch (error) {
        failCount++;
        console.error(`对点失败 (索引 ${i}):`, error);
        ElMessage.warning(
          `对点失败 (索引 ${i + 1}): ${error instanceof Error ? error.message : '未知错误'}`
        );
      }

      // 更新计数（使用已处理数量，避免 +1 溢出）
      const processed = i + 1;
      autoPointCurrentIndex.value = processed;
      autoPointProgress.value = Math.round((processed / selectedRows.value.length) * 100);

      // 轻微节流，避免请求过快
      await new Promise((resolve) => setTimeout(resolve, 50));
    }

    if (autoPointAbortController.value && !autoPointAbortController.value.signal.aborted) {
      autoPointStatus.value = "success";
      ElMessage.success(`批量对点完成，成功: ${successCount}条，失败: ${failCount}条`);
    }
  } catch (error) {
    if (error === "cancel") {
      ElMessage.info("已取消批量对点操作");
      return;
    }
    autoPointStatus.value = "exception";
    const errorInstance = error instanceof Error ? error : new Error(String(error));
    ElMessage.error(`批量对点失败: ${errorInstance.message}`);
    emit("error", errorInstance);
  } finally {
    setTimeout(() => {
      isAutoPointing.value = false;
      isAutoPointingLoading.value = false;
      autoPointAbortController.value = null;
    }, 1000);
    await refreshData();
  }
}

async function handleAutoPoint() {
  // 正在自动对点则取消
  if (isAutoPointing.value) {
    cancelAutoPoint();
    return;
  }
  try {
    await ElMessageBox.confirm("确认开始自动对点？", "自动对点", {
      confirmButtonText: "确定",
      cancelButtonText: "取消",
      type: "warning",
    });
    await startAutoPoint();
  } catch (error) {
    if (error !== "cancel") {
      const errorInstance = error instanceof Error ? error : new Error(String(error));
      ElMessage.error(`操作失败: ${errorInstance.message}`);
      emit("error", errorInstance);
    }
  }
}

async function startAutoPoint() {
  isAutoPointing.value = true;
  isAutoPointingLoading.value = true;
  autoPointProgress.value = 0;
  autoPointCurrentIndex.value = 0;
  autoPointStatus.value = "";

  try {
    // 汇总全量数据
    let allData: HmiBatchDeleteRow[] = [];
    if (total.value > pagination.limit) {
      const originalOffset = pagination.offset;
      const originalLimit = pagination.limit;
      const totalPages = Math.ceil(total.value / originalLimit);
      for (let page = 1; page <= totalPages; page++) {
        pagination.offset = (page - 1) * originalLimit;
        await handlePaginationChange();
        allData = allData.concat([...tableData.value]);
      }
      // 恢复页码
      pagination.offset = originalOffset;
      await handlePaginationChange();
    } else {
      allData = [...tableData.value];
    }

    autoPointTotalCount.value = allData.length;
    autoPointAbortController.value = new AbortController();
    isAutoPointingLoading.value = false;

    for (let i = 0; i < allData.length; i++) {
      if (!autoPointAbortController.value || autoPointAbortController.value.signal.aborted) {
        // ElMessage.info("自动对点已取消");
        break;
      }
      const row = allData[i];
      try {
        await batchPoint([row]);
        autoPointCurrentIndex.value = i + 1;
        autoPointProgress.value = Math.round(((i + 1) / allData.length) * 100);
        await new Promise((resolve) => setTimeout(resolve, 50));
      } catch (error) {
        console.error(`对点失败 (索引 ${i}):`, error);
        ElMessage.warning(`对点失败 (索引 ${i + 1}): ${error instanceof Error ? error.message : '未知错误'}`);
      }
    }

    if (autoPointAbortController.value && !autoPointAbortController.value.signal.aborted) {
      autoPointStatus.value = "success";
      ElMessage.success("自动对点完成");
    }
  } catch (error) {
    autoPointStatus.value = "exception";
    const errorInstance = error instanceof Error ? error : new Error(String(error));
    ElMessage.error(`自动对点失败: ${errorInstance.message}`);
    emit("error", errorInstance);
  } finally {
    setTimeout(() => {
      isAutoPointing.value = false;
      isAutoPointingLoading.value = false;
      autoPointAbortController.value = null;
    }, 1000);
    // 刷新以反映最新状态
    await refreshData();
  }
}

function cancelAutoPoint() {
  if (autoPointAbortController.value) {
    autoPointAbortController.value.abort();
  }
  isAutoPointing.value = false;
  isAutoPointingLoading.value = false;
  autoPointAbortController.value = null;
  autoPointProgress.value = 0;
  autoPointCurrentIndex.value = 0;
  autoPointStatus.value = "";
  ElMessage.info("自动对点已取消");
}

async function handleRefresh() {
  try {
    await refreshData();
    emit("data-loaded", tableData.value);
    ElMessage.success("刷新成功");
  } catch (error) {
    const errorInstance = error instanceof Error ? error : new Error(String(error));
    emit("error", errorInstance);
  }
}

// 导出表格数据
async function handleExport() {
  try {
    if (!tableData.value.length) {
      ElMessage.warning("暂无数据可导出");
      return;
    }

    // 生成导出列配置
    const columns = generateExportColumns(props.config.columns);

    const filename = route.meta.title as string;
    // 导出配置
    const exportConfig = {
      filename: `${filename}-${new Date().toISOString().slice(0, 10)}`,
      sheetName: `${filename}数据`,
      columns,
      data: tableData.value,
    };

    await exportToExcel(exportConfig);
  } catch (error) {
    console.error("导出失败:", error);
    ElMessage.error("导出失败，请重试");
  }
}

// 行操作
function handleDownload(row: HmiBatchDeleteRow) {
  const id = row[props.config.idKey];
  confirmOperation(OperationType.DOWNLOAD, "确认下载该数据？", () => downloadData(id));
}

function handleReset(row: HmiBatchDeleteRow) {
  const id = row[props.config.idKey];
  confirmOperation(OperationType.RESET, "确认重置该数据？", () => resetRow(id));
}

function handleDelete(row: HmiBatchDeleteRow) {
  const id = row[props.config.idKey];
  confirmOperation(OperationType.DELETE, "确认删除该数据？", () => deleteRow(id));
}

function handleTrans(row: HmiBatchDeleteRow) {
  confirmOperation(OperationType.TRANS, "确认传动该数据？", () => transRow(row));
}

function handlePoint(row: HmiBatchDeleteRow) {
  confirmOperation(OperationType.POINT, "确认对点该数据？", () => batchPoint([row]));
}

// 初始化
onMounted(async () => {
  try {
    await fetchData();
    emit("data-loaded", tableData.value);
  } catch (error) {
    const errorInstance = error instanceof Error ? error : new Error(String(error));
    emit("error", errorInstance);
  }
});
</script>

<style lang="scss" scoped>
.hmi-batch-delete-table {
  &__toolbar {
    margin-bottom: 16px;

    &--actions {
      display: flex;
      gap: 8px;
      flex-wrap: wrap;
    }
  }

  &__content {
    width: 100%;
  }

  &__pagination {
    margin-top: 16px;
    display: flex;
    justify-content: flex-end;
  }
}

.auto-point-progress {
  margin-bottom: 16px;
  .progress-info {
    margin-top: 8px;
    text-align: center;
    font-size: 14px;
    color: #666;
  }
}
</style>
